package com.planw.beetl.sql.search;

import com.intellij.openapi.application.Application;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.application.QueryExecutorBase;
import com.intellij.psi.*;
import com.intellij.util.Processor;
import com.planw.beetl.utils.JavaService;
import org.apache.commons.lang3.StringUtils;
import org.jetbrains.annotations.NotNull;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class BeetlSqlJavaMapperQueryExecutorBase extends QueryExecutorBase<PsiElement, PsiElement> {

    @Override
    public void processQuery(@NotNull PsiElement element, @NotNull Processor<PsiElement> consumer) {
        if (!(element instanceof PsiTypeParameterListOwner)) return;
        if (!(element instanceof PsiMethod)) {
            return;
        }
        final Application application = ApplicationManager.getApplication();
       
        application.runReadAction(new Runnable() {
            @Override
            public void run() {
                PsiMethod psiMethod = (PsiMethod) element;
                PsiClass psiClass = psiMethod.getContainingClass();
                if (null == psiClass) return;
                toSearchSql(psiClass, psiMethod, consumer);
            }
        });
    }

    protected void toSearchSql(PsiClass psiClass, PsiMethod psiMethod, Processor<PsiElement> consumer) {
        JavaService javaService = JavaService.getInstance(psiClass.getProject());
        if (!psiClass.isInterface() || !javaService.checkIsBeetlSqlClass(psiClass)) {
            return;
        }
        PsiClassType[] classTypes = psiClass.getExtendsListTypes();
        String sqlFileName = null;
        for (PsiClassType classType : classTypes) {
            if (!classType.getInternalCanonicalText().startsWith("org.beetl.sql.core.mapper.BaseMapper")) {
                continue;
            }
            sqlFileName = classType.getParameters()[0].getPresentableText();
        }
        if (StringUtils.isBlank(sqlFileName)) {
            return;
        }
        Map<String, PsiMethod> psiMethodMap = new HashMap<>();
        psiMethodMap.put(psiMethod.getName(), psiMethod);

        List<PsiFile> fileList = javaService.getAllBeetlSqlFiles(psiClass.getProject(), sqlFileName);
        if (fileList == null || fileList.isEmpty()) {
            return;
        }
        Map<String, List<PsiElement>> targetSqlElement = javaService.buildTargetPsiElement(fileList, psiMethodMap);
        if (targetSqlElement == null || targetSqlElement.isEmpty()) {
            return;
        }
        List<PsiElement> psiElements = targetSqlElement.get(psiMethod.getName());
        if (psiElements == null || psiElements.isEmpty()) {
            return;
        }
        for (PsiElement psiElement : psiElements) {
            consumer.process(psiElement);
        }

    }
}
